home *** CD-ROM | disk | FTP | other *** search
/ 220 Jogos / 220 jogos.iso / classicos / genius3 / SIMON.CPP < prev    next >
Encoding:
C/C++ Source or Header  |  2002-09-29  |  28.6 KB  |  1,070 lines

  1. /*****************************************
  2. /*        Javier Barandiaran Martirena     *
  3. /*                   2002                     *
  4. /*                                         *
  5. /* http://www.geocities.com/opengladiator*
  6. /*                                         *
  7. /*        Codigo Base Jeff Molofee          *
  8. /*        http://nehe.gamedev.net          *
  9. /*****************************************/
  10. #include <windows.h>        // Header File For Windows
  11. #include <gl\gl.h>            // Header File For The OpenGL32 Library
  12. #include <gl\glu.h>            // Header File For The GLu32 Library
  13. #include <gl\glaux.h>        // Header File For The Glaux Library
  14. #include <stdarg.h>    
  15. #include <stdio.h>
  16. #include "reloj.h"
  17. #include "texturas.h"
  18.  
  19.     
  20.  
  21. HDC            hDC=NULL;        // Private GDI Device Context
  22. HGLRC        hRC=NULL;        // Permanent Rendering Context
  23. HWND        hWnd=NULL;        // Holds Our Window Handle
  24. HINSTANCE    hInstance;        // Holds The Instance Of The Application
  25.  
  26. bool    keys[256];            // Array Used For The Keyboard Routine
  27. bool    active=TRUE;        // Window Active Flag Set To TRUE By Default
  28. bool    fullscreen=TRUE;    // Fullscreen Flag Set To Fullscreen Mode By Default
  29.  
  30. int h,f;
  31.  
  32. const numtext=15;
  33. TexturaTGA *texturas[numtext];
  34.  
  35. GLuint    base;
  36.  
  37. int mouse_x, mouse_y;    
  38.  
  39. reloj *mireloj;
  40.  
  41. int estado=0;        //textura que se dibuja(boton rojo pulsado,boton verde,...)
  42.                     //estado=0 ningun boton iluminado
  43.                     //estado=1 boton verde pulsado
  44.                     //estado=2 boton rojo pulsado
  45.                     //estado=3 boton azul pulsado
  46.                     //estado=4 boton amariilo pulsado
  47.  
  48. float Tultimo=0.0f;            //Tiempo transcurrido desde que se encendio un boton
  49. float Tencendido=950.0f;    //Tiempo que permanece encendido un boton
  50. float Tseparacion=1000;        //Tiempo de separacion entre cada boton
  51. float Trespuesta=3050;        //Tiempo maximo de respuesta para el jugador
  52.  
  53. int numpulsaciones=0;        //numero de pulsaciones realizadas por el jugador hasta el momento
  54.  
  55. int secuencia[20];            //array de estados(1,2,3,4), la secuencia de luces
  56. int actual=0;                //elemento actual de la secuencia para cuando se repite
  57. int numgeneradas=0;            //numero de luces generadas hasta el momento
  58.  
  59. int nivel[6]={8,10,12,14,16,18};    //longitud en numero de luces de cada nivel
  60. int nact=0;                    //nivel actual(0,1,2,3)
  61.  
  62. bool generando=TRUE;    //indica si se esta generando una secuencia 
  63. bool pulsacion=FALSE;    //indica si el jugador a pulsado un boton
  64. bool inicio=TRUE;        //indica si estamos en el menu de inicio
  65. bool salir=FALSE;
  66. bool repit=FALSE;
  67. bool yo=FALSE;
  68. bool mnivel=FALSE;        //indica si estamos en el menu de niveles
  69. bool fallo=FALSE;        //indica si el jugador ha fallado
  70. bool triunfo=FALSE;        //indica si el jugador ha completado la secuencia
  71.  
  72. typedef struct
  73. {
  74.     int cabecera;
  75.     int opciones;
  76. }Smenu;
  77. Smenu menus[4];            //guarda el ID de la textura para cada menu
  78.                         //menus[0]    inicio
  79.                         //menus[1]    triunfo
  80.                         //menus[2]    fracaso
  81.                         //menus[3]    nivel
  82.  
  83. int botonp;                //que boton del menu esta pulsado
  84.  
  85.  
  86. int val;
  87.  
  88. char *sonidos[5]={"","data\\verde.wav","data\\rojo.wav","data\\azul.wav","data\\amarillo.wav"};
  89.  
  90. LRESULT    CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);    // Declaration For WndProc
  91.  
  92. GLvoid BuildFont(GLvoid)                                // Build Our Bitmap Font
  93. {
  94.     HFONT    font;                                        // Windows Font ID
  95.     HFONT    oldfont;                                    // Used For Good House Keeping
  96.  
  97.     base = glGenLists(96);                                // Storage For 96 Characters
  98.  
  99.     font = CreateFont(    -24,                            // alto Of Font
  100.                         0,                                // ancho Of Font
  101.                         0,                                // Angle Of Escapement
  102.                         0,                                // Orientation Angle
  103.                         FW_BOLD,                        // Font Weight
  104.                         FALSE,                            // Italic
  105.                         FALSE,                            // Underline
  106.                         FALSE,                            // Strikeout
  107.                         ANSI_CHARSET,                    // Character Set Identifier
  108.                         OUT_TT_PRECIS,                    // Output Precision
  109.                         CLIP_DEFAULT_PRECIS,            // Clipping Precision
  110.                         ANTIALIASED_QUALITY,            // Output Quality
  111.                         FF_DECORATIVE|VARIABLE_PITCH,        // Family And Pitch
  112.                         "Arial");                    // Font Name
  113.  
  114.     oldfont = (HFONT)SelectObject(hDC, font);           // Selects The Font We Want
  115.     wglUseFontBitmaps(hDC, 32, 96, base);                // Builds 96 Characters Starting At Character 32
  116.     SelectObject(hDC, oldfont);                            // Selects The Font We Want
  117.     DeleteObject(font);                                    // Delete The Font
  118. }
  119.  
  120. GLvoid KillFont(GLvoid)                                    // Delete The Font List
  121. {
  122.     glDeleteLists(base, 96);                            // Delete All 96 Characters
  123. }
  124.  
  125. GLvoid glPrint(const char *fmt, ...)                    // Custom GL "Print" Routine
  126. {
  127.     char        text[256];                                // Holds Our String
  128.     va_list        ap;                                        // Pointer To List Of Arguments
  129.  
  130.     if (fmt == NULL)                                    // If There's No Text
  131.         return;                                            // Do Nothing
  132.  
  133.     va_start(ap, fmt);                                    // Parses The String For Variables
  134.         vsprintf(text, fmt, ap);                        // And Converts Symbols To Actual Numbers
  135.     va_end(ap);                                            // Results Are Stored In Text
  136.  
  137.     glPushAttrib(GL_LIST_BIT);                            // Pushes The Display List Bits
  138.     glListBase(base - 32);                                // Sets The Base Character to 32
  139.     glCallLists(strlen(text), GL_UNSIGNED_BYTE, text);    // Draws The Display List Text
  140.     glPopAttrib();                                        // Pops The Display List Bits
  141. }
  142.  
  143. GLvoid ReSizeGLScene(GLsizei ancho, GLsizei alto)        // Resize And Initialize The GL Window
  144. {
  145.     if (alto==0)                                        // Prevent A Divide By Zero By
  146.     {
  147.         alto=1;                                        // Making alto Equal One
  148.     }
  149.  
  150.     glViewport(0,0,ancho,alto);                        // Reset The Current Viewport
  151.  
  152.     glMatrixMode(GL_PROJECTION);                        // Select The Projection Matrix
  153.     glLoadIdentity();                                    // Reset The Projection Matrix
  154.  
  155.     // Calculate The Aspect Ratio Of The Window
  156.     //gluPerspective(45.0f,(GLfloat)ancho/(GLfloat)alto,0.1f,100.0f);
  157.     glOrtho(0.0f,ancho,alto,0.0f,-1.0f,1.0f);
  158.     
  159.     glMatrixMode(GL_MODELVIEW);                            // Select The Modelview Matrix
  160.     glLoadIdentity();                                    // Reset The Modelview Matrix
  161. }
  162.  
  163. int InitGL(GLvoid)                                        // All Setup For OpenGL Goes Here
  164. {
  165.     glShadeModel(GL_FLAT);                            // Enable Smooth Shading
  166.     glClearColor(0.0f, 0.0f, 0.0f, 0.5f);                // Black Background
  167.     glDisable(GL_DEPTH_TEST);                            // Enables Depth Testing
  168.     glDepthFunc(GL_LEQUAL);                                // The Type Of Depth Testing To Do
  169.     glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);    // Really Nice Perspective Calculations
  170.  
  171.     glEnable(GL_TEXTURE_2D);
  172.     
  173.     //glEnable(GL_BLEND);
  174.     glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
  175.     BuildFont();
  176.  
  177.     for(int t=0;t<numtext;t++)
  178.     {
  179.         texturas[t]=(TexturaTGA*)malloc(sizeof(TexturaTGA));
  180.     }
  181.  
  182.     /*TCHAR pathAplicacion[MAX_PATH];
  183.     GetModuleFileName(NULL, pathAplicacion, MAX_PATH);
  184.     CString nombrePath=pathAplicacion;
  185.     int pos;
  186.     pos=nombrePath.ReverseFind('\\');
  187.  
  188.     nombrePath=nombrePath.Left(pos+1);
  189.     nombrePath+=_T("\data\simon.tga");*/
  190.  
  191.     CargaTGA(texturas[0],"data\\simon.tga");
  192.     CargaTGA(texturas[1],"data\\simonv.tga");
  193.     CargaTGA(texturas[2],"data\\simonr.tga");
  194.     CargaTGA(texturas[3],"data\\simonb.tga");
  195.     CargaTGA(texturas[4],"data\\simona.tga");
  196.     //botones
  197.     CargaTGA(texturas[6],"data\\menu.tga");
  198.     
  199.     
  200.     menus[0].opciones=7;
  201.     menus[0].cabecera=11;
  202.     CargaTGA(texturas[11],"data\\men.tga");
  203.     CargaTGA(texturas[7],"data\\Inicio.tga");
  204.     
  205.     menus[1].opciones=8;
  206.     menus[1].cabecera=13;
  207.     CargaTGA(texturas[8],"data\\triunfo.tga");
  208.     CargaTGA(texturas[13],"data\\fel.tga");
  209.     
  210.     menus[2].opciones=9;
  211.     menus[2].cabecera=14;
  212.     CargaTGA(texturas[9],"data\\fallo.tga");
  213.     CargaTGA(texturas[14],"data\\FAL.tga");
  214.     
  215.     menus[3].opciones=10;
  216.     menus[3].cabecera=12;
  217.     CargaTGA(texturas[10],"data\\niveles.tga");
  218.     CargaTGA(texturas[12],"data\\dif.tga");
  219.     
  220.     CargaTGA(texturas[5],"data\\yo.tga");
  221.  
  222.     srand(mireloj->TimerGetTime());
  223.     
  224.     
  225.     return TRUE;        
  226. }
  227.  
  228.  
  229. void ReiniciarJuego(int nact)
  230. {
  231.     inicio=FALSE;
  232.     fallo=FALSE;
  233.     triunfo=FALSE;
  234.     generando=TRUE;
  235.     pulsacion=FALSE;
  236.     numgeneradas=0;
  237.     estado=0;    
  238.     numpulsaciones=0;
  239.     Tencendido=950.0f;
  240.     Tseparacion=1000;
  241.     Trespuesta=3050;
  242. }
  243.  
  244. int SelecMenu(int mx,int my,int menu)
  245. {
  246.     GLuint alpha,byte,bytepp,alto,ancho;
  247.     int x,y,boton;
  248.     int t=menus[menu].opciones;
  249.     float factorx=300.0f/texturas[t]->ancho;
  250.     float factory=210.0f/texturas[t]->alto;
  251.  
  252.     
  253.     bytepp=texturas[t]->bpp/8;
  254.     alto=texturas[t]->alto;
  255.     ancho=texturas[t]->ancho;
  256.     x=int((mx-270)/factorx);
  257.     y=int((400-my)/factory);
  258.     boton=-1;
  259.     if(mx>270&& mx<570 && my<400 &&my>190)
  260.     {
  261.         if(mnivel)
  262.         {
  263.             if(mx<420)
  264.             {
  265.                 if(my<260)
  266.                     boton=0;
  267.                 else
  268.                 {
  269.                     if(my<330)
  270.                         boton=1;
  271.                     else
  272.                         boton=2;
  273.                 }
  274.             }
  275.             else
  276.             {
  277.                 if(my<260)
  278.                     boton=3;
  279.                 else
  280.                 {
  281.                     if(my<330)
  282.                         boton=4;
  283.                     else
  284.                         boton=5;
  285.                 }
  286.             }
  287.         }    
  288.         else
  289.         {
  290.             if(my<260)
  291.                 boton=0;
  292.             else
  293.             {
  294.                 if(my<330)
  295.                     boton=1;
  296.                 else
  297.                     boton=2;
  298.             }
  299.         }
  300.         
  301.         if(boton!=-1||yo)
  302.         {
  303.             byte=bytepp-1+((y*ancho)+x)*bytepp;
  304.             alpha=texturas[t]->imageData[byte];    
  305.             if (alpha!=0)
  306.             {
  307.                 if(yo)
  308.                     return 1;
  309.                 return boton;
  310.             }
  311.         }
  312.     }
  313.     return -1;
  314. }
  315.  
  316. void MostrarMenu(int menu)
  317. {
  318.  
  319.     int t=menus[menu].opciones;
  320.     glEnable(GL_BLEND);
  321.     glBindTexture(GL_TEXTURE_2D, texturas[menus[menu].cabecera]->texID);
  322.     glBegin(GL_QUADS);
  323.         glTexCoord2d(1,0);
  324.         glVertex2d(590,190);    
  325.         glTexCoord2d(1,1);
  326.         glVertex2d(590,130);
  327.         glTexCoord2d(0,1);    
  328.         glVertex2d(250,130);
  329.         glTexCoord2d(0,0);
  330.         glVertex2d(250,190);    
  331.     glEnd();
  332.     glBindTexture(GL_TEXTURE_2D, texturas[6]->texID);
  333.     glBegin(GL_QUADS);
  334.         glTexCoord2d(1,0);
  335.         glVertex2d(570,400);    
  336.         glTexCoord2d(1,1);
  337.         glVertex2d(570,190);
  338.         glTexCoord2d(0,1);    
  339.         glVertex2d(270,190);
  340.         glTexCoord2d(0,0);
  341.         glVertex2d(270,400);    
  342.     glEnd();
  343.     
  344.     glBindTexture(GL_TEXTURE_2D, texturas[t]->texID);
  345.     glBegin(GL_QUADS);
  346.         glTexCoord2d(1,0);
  347.         glVertex2d(570,400);    
  348.         glTexCoord2d(1,1);
  349.         glVertex2d(570,190);
  350.         glTexCoord2d(0,1);    
  351.         glVertex2d(270,190);
  352.         glTexCoord2d(0,0);
  353.         glVertex2d(270,400);    
  354.     glEnd();
  355.     glDisable(GL_BLEND);
  356. }
  357.  
  358. bool boton(int mx, int my)
  359. {
  360.     GLuint alpha,byte,bytepp,alto,ancho;
  361.     int x,y;
  362.     float factorx=800.0/texturas[0]->ancho;
  363.     float factory=600.0/texturas[0]->alto;
  364.             
  365.     //acierto: si el impacto esta en el cuadrado y el pixel alpha
  366.     //de la textura no es negro
  367.     bytepp=texturas[0]->bpp/8;
  368.     alto=texturas[0]->alto;
  369.     ancho=texturas[0]->ancho;
  370.     x=int(mx/factorx);
  371.     y=int((600-my)/factory);
  372.     byte=bytepp-1+((y*ancho)+x)*bytepp;
  373.     alpha=texturas[0]->imageData[byte];    
  374.     if (alpha!=0)
  375.     {
  376.         return true;
  377.     }
  378.     return false;
  379. }
  380.  
  381. void Pulsa(int mx,int my)
  382. {
  383.     if (boton(mx,my))
  384.     {
  385.         
  386.         pulsacion=TRUE;
  387.  
  388.         if(mx<400)
  389.         {
  390.             if(my>300)
  391.             {
  392.                 estado=4;
  393.             }
  394.             else
  395.                 estado=1;
  396.             }
  397.             else
  398.             {
  399.                 if(my>300)
  400.                     estado=3;
  401.                 else
  402.                     estado=2;
  403.             }        
  404.         }
  405.         else
  406.             estado=0;
  407. }
  408. void RecibiendoSecuencia()
  409. {
  410.     if(pulsacion)                    //SI HAY PULSACION
  411.     {
  412.         pulsacion=FALSE;
  413.         if(estado!=secuencia[numpulsaciones])    //SI NO COINCIDE
  414.         {
  415.             fallo=TRUE;
  416.             PlaySound("data\\error2.wav",NULL,0);
  417.         }
  418.         else                                    //COINCIDE
  419.         {
  420.             PlaySound(sonidos[estado],NULL,1);
  421.             numpulsaciones++;
  422.             Tultimo=mireloj->TimerGetTime();
  423.         }
  424.     }
  425.     else 
  426.     {
  427.         if ((mireloj->TimerGetTime()-Tultimo)>Tencendido)
  428.         {
  429.             estado=0;
  430.         }
  431.         if ((mireloj->TimerGetTime()-Tultimo)>Trespuesta)    //SI SE HA PASADO EL TIEMPO DE RESPUESTA
  432.         {
  433.             fallo=TRUE;
  434.             PlaySound("data\\error2.wav",NULL,0);
  435.         }    
  436.     }
  437. }
  438.  
  439. void Repetir()
  440. {
  441.         if ((mireloj->TimerGetTime()-Tultimo)>Tseparacion)
  442.         {
  443.             estado=secuencia[actual];
  444.             PlaySound(sonidos[estado],NULL,1);
  445.             actual++;
  446.             Tultimo=mireloj->TimerGetTime();
  447.         }
  448.         else if ((mireloj->TimerGetTime()-Tultimo)>Tencendido)
  449.             estado=0;
  450. }
  451.  
  452. void Generar()
  453. {
  454.     if(actual<numgeneradas)            //REPETIMOS LA SECUENCIA GENERADA
  455.     {
  456.         Repetir();
  457.     }
  458.     else                    
  459.     {
  460.         if ((mireloj->TimerGetTime()-Tultimo)>Tseparacion) //GENERAMOS UNO MAS
  461.         {
  462.  
  463.             //
  464.             val=1+rand()%4;
  465.             estado=val;
  466.             PlaySound(sonidos[estado],NULL,1);
  467.             Tultimo=mireloj->TimerGetTime();
  468.             secuencia[numgeneradas]=estado;
  469.             numgeneradas++;
  470.             actual=0;
  471.             generando=FALSE;
  472.             //Reducimos los tiempos
  473.             //Trespuesta-=50;
  474.             Tencendido-=100.0;
  475.             Tseparacion-=100.0;
  476.             if(Tseparacion<=200.0)
  477.             {
  478.                 Tseparacion=200.0;
  479.             }
  480.             if(Tencendido<=150.0)
  481.             {
  482.                 Tencendido=150.0;
  483.             }
  484.  
  485.         }
  486.         else if ((mireloj->TimerGetTime()-Tultimo)>Tencendido)
  487.             estado=0;        
  488.     }
  489. }
  490.  
  491. int DrawGLScene(GLvoid)                            
  492. {    
  493.     glClear(GL_COLOR_BUFFER_BIT);    
  494.     glLoadIdentity();
  495.     if(inicio)
  496.         MostrarMenu(0);
  497.     else if (mnivel)
  498.     {
  499.         MostrarMenu(3);
  500.     }
  501.     else if(yo)
  502.     {
  503.         glBindTexture(GL_TEXTURE_2D, texturas[5]->texID);
  504.         glBegin(GL_TRIANGLE_STRIP);
  505.                 glTexCoord2d(0,0);
  506.             glVertex2d(0,599);    
  507.                 glTexCoord2d(0,1);    
  508.             glVertex2d(0,0);
  509.                 glTexCoord2d(1,0);
  510.             glVertex2d(799,599);
  511.                 glTexCoord2d(1,1);
  512.             glVertex2d(799,0);
  513.         glEnd();
  514.     }
  515.     
  516.     else
  517.     {
  518.         if(repit)
  519.         {    
  520.             Repetir();
  521.             if(actual==numgeneradas)
  522.             {
  523.                 repit=FALSE;
  524.                 fallo=TRUE;
  525.             }
  526.         }
  527.         if(generando)    //GENERANDO SECUENCIA
  528.             Generar();
  529.         else        //LA SECUENCIA HA SIDO GENERADA
  530.         {
  531.             if(!fallo && !triunfo)
  532.             {
  533.                 if(numpulsaciones<numgeneradas)        //TODAVIA FALTAN PULSACIONES
  534.                 {
  535.                     RecibiendoSecuencia();    
  536.                 }
  537.                 else            //YA SE HA PULSADO TODA LA SECUENCIA
  538.                 {
  539.                     
  540.                     if(numpulsaciones==nivel[nact])    //SE HA COMPLETADO EL NIVEL
  541.                     {
  542.                         triunfo=TRUE;
  543.                         PlaySound("data\\TRIUNFO.WAV",NULL,0);
  544.                     }
  545.                     else                            //TODAVIA NO SE HA COMPLETADO EL NIVEL
  546.                     {
  547.                         generando=TRUE;
  548.                         srand(mireloj->TimerGetTime());
  549.                         numpulsaciones=0;                
  550.                     }
  551.                 }
  552.             }
  553.         }
  554.             
  555.         glBindTexture(GL_TEXTURE_2D, texturas[estado]->texID);
  556.         glBegin(GL_TRIANGLE_STRIP);
  557.                 glTexCoord2d(0,0);
  558.             glVertex2d(0,599);    
  559.                 glTexCoord2d(0,1);    
  560.             glVertex2d(0,0);
  561.                 glTexCoord2d(1,0);
  562.             glVertex2d(799,599);
  563.                 glTexCoord2d(1,1);
  564.             glVertex2d(799,0);
  565.         glEnd();
  566.         
  567.         if(fallo)
  568.         {
  569.             if ((mireloj->TimerGetTime()-Tultimo)>200)
  570.             {
  571.                 estado++;
  572.                 if(estado==5)
  573.                     estado=1;
  574.                 Tultimo=mireloj->TimerGetTime();
  575.             }
  576.             MostrarMenu(2);
  577.         }
  578.         if(triunfo)
  579.         {
  580.             if ((mireloj->TimerGetTime()-Tultimo)>100)
  581.             {
  582.                 estado++;
  583.                 if(estado>=5)
  584.                     estado=1;
  585.                 Tultimo=mireloj->TimerGetTime();
  586.             }
  587.             MostrarMenu(1);
  588.         }
  589.         /*glLineWidth(1.0);
  590.         glBegin(GL_LINES);
  591.         glColor3f(1.0,0.0,0.0);
  592.             glVertex2f((float)mouse_x-10.0f,(float)mouse_y);
  593.             glVertex2f((float)mouse_x+10.0f,(float)mouse_y);
  594.             glVertex2f((float)mouse_x,(float)mouse_y-5.0f);
  595.             glVertex2f((float)mouse_x,(float)mouse_y+5.0f);
  596.         glEnd();*/
  597.         glColor4f(1.0,0.0,0.0,1.0);
  598.         /*glRasterPos2f(25,300);
  599.         glPrint("Separacion %f",Tseparacion);
  600.         glRasterPos2f(25,400);
  601.         glPrint("Encendido %f",Tencendido);*/
  602.         glDisable(GL_BLEND);
  603.         glRasterPos2f(25,550);
  604.         glPrint("Level %d",nact);
  605.         glColor4f(1.0,1.0,1.0,1.0);
  606.     }
  607.     
  608.     
  609.  
  610.  
  611.     return TRUE;                                        // Everything Went OK
  612. }
  613.  
  614. GLvoid KillGLWindow(GLvoid)                                // Properly Kill The Window
  615. {
  616.     if (fullscreen)                                        // Are We In Fullscreen Mode?
  617.     {
  618.         ChangeDisplaySettings(NULL,0);                    // If So Switch Back To The Desktop
  619.         ShowCursor(TRUE);                                // Show Mouse Pointer
  620.     }
  621.  
  622.     if (hRC)                                            // Do We Have A Rendering Context?
  623.     {
  624.         if (!wglMakeCurrent(NULL,NULL))                    // Are We Able To Release The DC And RC Contexts?
  625.         {
  626.             MessageBox(NULL,"Release Of DC And RC Failed.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
  627.         }
  628.  
  629.         if (!wglDeleteContext(hRC))                        // Are We Able To Delete The RC?
  630.         {
  631.             MessageBox(NULL,"Release Rendering Context Failed.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
  632.         }
  633.         hRC=NULL;                                        // Set RC To NULL
  634.     }
  635.  
  636.     if (hDC && !ReleaseDC(hWnd,hDC))                    // Are We Able To Release The DC
  637.     {
  638.         MessageBox(NULL,"Release Device Context Failed.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
  639.         hDC=NULL;                                        // Set DC To NULL
  640.     }
  641.  
  642.     if (hWnd && !DestroyWindow(hWnd))                    // Are We Able To Destroy The Window?
  643.     {
  644.         MessageBox(NULL,"Could Not Release hWnd.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
  645.         hWnd=NULL;                                        // Set hWnd To NULL
  646.     }
  647.  
  648.     if (!UnregisterClass("OpenGL",hInstance))            // Are We Able To Unregister Class
  649.     {
  650.         MessageBox(NULL,"Could Not Unregister Class.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
  651.         hInstance=NULL;                                    // Set hInstance To NULL
  652.     }
  653. }
  654.  
  655. /*    This Code Creates Our OpenGL Window.  Parameters Are:                    *
  656.  *    title            - Title To Appear At The Top Of The Window                *
  657.  *    ancho            - ancho Of The GL Window Or Fullscreen Mode                *
  658.  *    alto            - alto Of The GL Window Or Fullscreen Mode            *
  659.  *    bits            - Number Of Bits To Use For Color (8/16/24/32)            *
  660.  *    fullscreenflag    - Use Fullscreen Mode (TRUE) Or Windowed Mode (FALSE)    */
  661.  
  662. BOOL CreateGLWindow(char* title, int ancho, int alto, int bits, bool fullscreenflag)
  663. {
  664.     GLuint        PixelFormat;            // Holds The Results After Searching For A Match
  665.     WNDCLASS    wc;                        // Windows Class Structure
  666.     DWORD        dwExStyle;                // Window Extended Style
  667.     DWORD        dwStyle;                // Window Style
  668.     RECT        WindowRect;                // Grabs Rectangle Upper Left / Lower Right Values
  669.     WindowRect.left=(long)0;            // Set Left Value To 0
  670.     WindowRect.right=(long)ancho;        // Set Right Value To Requested ancho
  671.     WindowRect.top=(long)0;                // Set Top Value To 0
  672.     WindowRect.bottom=(long)alto;        // Set Bottom Value To Requested alto
  673.  
  674.     fullscreen=fullscreenflag;            // Set The Global Fullscreen Flag
  675.  
  676.     hInstance            = GetModuleHandle(NULL);                // Grab An Instance For Our Window
  677.     wc.style            = CS_HREDRAW | CS_VREDRAW | CS_OWNDC;    // Redraw On Size, And Own DC For Window.
  678.     wc.lpfnWndProc        = (WNDPROC) WndProc;                    // WndProc Handles Messages
  679.     wc.cbClsExtra        = 0;                                    // No Extra Window Data
  680.     wc.cbWndExtra        = 0;                                    // No Extra Window Data
  681.     wc.hInstance        = hInstance;                            // Set The Instance
  682.     wc.hIcon            = LoadIcon(NULL, IDI_WINLOGO);            // Load The Default Icon
  683.     wc.hCursor            = LoadCursor(NULL, IDC_ARROW);            // Load The Arrow Pointer
  684.     wc.hbrBackground    = NULL;                                    // No Background Required For GL
  685.     wc.lpszMenuName        = NULL;                                    // We Don't Want A Menu
  686.     wc.lpszClassName    = "OpenGL";                                // Set The Class Name
  687.  
  688.     if (!RegisterClass(&wc))                                    // Attempt To Register The Window Class
  689.     {
  690.         MessageBox(NULL,"Failed To Register The Window Class.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  691.         return FALSE;                                            // Return FALSE
  692.     }
  693.     
  694.     if (fullscreen)                                                // Attempt Fullscreen Mode?
  695.     {
  696.         DEVMODE dmScreenSettings;                                // Device Mode
  697.         memset(&dmScreenSettings,0,sizeof(dmScreenSettings));    // Makes Sure Memory's Cleared
  698.         dmScreenSettings.dmSize=sizeof(dmScreenSettings);        // Size Of The Devmode Structure
  699.         dmScreenSettings.dmPelsWidth    = ancho;                // Selected Screen ancho
  700.         dmScreenSettings.dmPelsHeight    = alto;                // Selected Screen alto
  701.         dmScreenSettings.dmBitsPerPel    = bits;                    // Selected Bits Per Pixel
  702.         dmScreenSettings.dmFields=DM_BITSPERPEL|DM_PELSWIDTH|DM_PELSHEIGHT;
  703.  
  704.         // Try To Set Selected Mode And Get Results.  NOTE: CDS_FULLSCREEN Gets Rid Of Start Bar.
  705.         if (ChangeDisplaySettings(&dmScreenSettings,CDS_FULLSCREEN)!=DISP_CHANGE_SUCCESSFUL)
  706.         {
  707.             // If The Mode Fails, Offer Two Options.  Quit Or Use Windowed Mode.
  708.             if (MessageBox(NULL,"The Requested Fullscreen Mode Is Not Supported By\nYour Video Card. Use Windowed Mode Instead?","NeHe GL",MB_YESNO|MB_ICONEXCLAMATION)==IDYES)
  709.             {
  710.                 fullscreen=FALSE;        // Windowed Mode Selected.  Fullscreen = FALSE
  711.             }
  712.             else
  713.             {
  714.                 // Pop Up A Message Box Letting User Know The Program Is Closing.
  715.                 MessageBox(NULL,"Program Will Now Close.","ERROR",MB_OK|MB_ICONSTOP);
  716.                 return FALSE;                                    // Return FALSE
  717.             }
  718.         }
  719.     }
  720.  
  721.     if (fullscreen)                                                // Are We Still In Fullscreen Mode?
  722.     {
  723.         dwExStyle=WS_EX_APPWINDOW;                                // Window Extended Style
  724.         dwStyle=WS_POPUP;                                        // Windows Style
  725.     }
  726.     else
  727.     {
  728.         dwExStyle=WS_EX_APPWINDOW | WS_EX_WINDOWEDGE;            // Window Extended Style
  729.         dwStyle=WS_OVERLAPPEDWINDOW;                            // Windows Style
  730.     }
  731.  
  732.     AdjustWindowRectEx(&WindowRect, dwStyle, FALSE, dwExStyle);        // Adjust Window To True Requested Size
  733.  
  734.     // Create The Window
  735.     if (!(hWnd=CreateWindowEx(    dwExStyle,                            // Extended Style For The Window
  736.                                 "OpenGL",                            // Class Name
  737.                                 title,                                // Window Title
  738.                                 dwStyle |                            // Defined Window Style
  739.                                 WS_CLIPSIBLINGS |                    // Required Window Style
  740.                                 WS_CLIPCHILDREN,                    // Required Window Style
  741.                                 0, 0,                                // Window Position
  742.                                 WindowRect.right-WindowRect.left,    // Calculate Window ancho
  743.                                 WindowRect.bottom-WindowRect.top,    // Calculate Window alto
  744.                                 NULL,                                // No Parent Window
  745.                                 NULL,                                // No Menu
  746.                                 hInstance,                            // Instance
  747.                                 NULL)))                                // Dont Pass Anything To WM_CREATE
  748.     {
  749.         KillGLWindow();                                // Reset The Display
  750.         MessageBox(NULL,"Window Creation Error.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  751.         return FALSE;                                // Return FALSE
  752.     }
  753.  
  754.     static    PIXELFORMATDESCRIPTOR pfd=                // pfd Tells Windows How We Want Things To Be
  755.     {
  756.         sizeof(PIXELFORMATDESCRIPTOR),                // Size Of This Pixel Format Descriptor
  757.         1,                                            // Version Number
  758.         PFD_DRAW_TO_WINDOW |                        // Format Must Support Window
  759.         PFD_SUPPORT_OPENGL |                        // Format Must Support OpenGL
  760.         PFD_DOUBLEBUFFER,                            // Must Support Double Buffering
  761.         PFD_TYPE_RGBA,                                // Request An RGBA Format
  762.         bits,                                        // Select Our Color Depth
  763.         0, 0, 0, 0, 0, 0,                            // Color Bits Ignored
  764.         0,                                            // No Alpha Buffer
  765.         0,                                            // Shift Bit Ignored
  766.         0,                                            // No Accumulation Buffer
  767.         0, 0, 0, 0,                                    // Accumulation Bits Ignored
  768.         16,                                            // 16Bit Z-Buffer (Depth Buffer)  
  769.         0,                                            // No Stencil Buffer
  770.         0,                                            // No Auxiliary Buffer
  771.         PFD_MAIN_PLANE,                                // Main Drawing Layer
  772.         0,                                            // Reserved
  773.         0, 0, 0                                        // Layer Masks Ignored
  774.     };
  775.     
  776.     if (!(hDC=GetDC(hWnd)))                            // Did We Get A Device Context?
  777.     {
  778.         KillGLWindow();                                // Reset The Display
  779.         MessageBox(NULL,"Can't Create A GL Device Context.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  780.         return FALSE;                                // Return FALSE
  781.     }
  782.  
  783.     if (!(PixelFormat=ChoosePixelFormat(hDC,&pfd)))    // Did Windows Find A Matching Pixel Format?
  784.     {
  785.         KillGLWindow();                                // Reset The Display
  786.         MessageBox(NULL,"Can't Find A Suitable PixelFormat.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  787.         return FALSE;                                // Return FALSE
  788.     }
  789.  
  790.     if(!SetPixelFormat(hDC,PixelFormat,&pfd))        // Are We Able To Set The Pixel Format?
  791.     {
  792.         KillGLWindow();                                // Reset The Display
  793.         MessageBox(NULL,"Can't Set The PixelFormat.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  794.         return FALSE;                                // Return FALSE
  795.     }
  796.  
  797.     if (!(hRC=wglCreateContext(hDC)))                // Are We Able To Get A Rendering Context?
  798.     {
  799.         KillGLWindow();                                // Reset The Display
  800.         MessageBox(NULL,"Can't Create A GL Rendering Context.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  801.         return FALSE;                                // Return FALSE
  802.     }
  803.  
  804.     if(!wglMakeCurrent(hDC,hRC))                    // Try To Activate The Rendering Context
  805.     {
  806.         KillGLWindow();                                // Reset The Display
  807.         MessageBox(NULL,"Can't Activate The GL Rendering Context.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  808.         return FALSE;                                // Return FALSE
  809.     }
  810.  
  811.     ShowWindow(hWnd,SW_SHOW);                        // Show The Window
  812.     SetForegroundWindow(hWnd);                        // Slightly Higher Priority
  813.     SetFocus(hWnd);                                    // Sets Keyboard Focus To The Window
  814.     ReSizeGLScene(ancho, alto);                    // Set Up Our Perspective GL Screen
  815.  
  816.     if (!InitGL())                                    // Initialize Our Newly Created GL Window
  817.     {
  818.         KillGLWindow();                                // Reset The Display
  819.         MessageBox(NULL,"Initialization Failed.","ERROR",MB_OK|MB_ICONEXCLAMATION);
  820.         return FALSE;                                // Return FALSE
  821.     }
  822.  
  823.     return TRUE;                                    // Success
  824. }
  825.  
  826. LRESULT CALLBACK WndProc(    HWND    hWnd,            // Handle For This Window
  827.                             UINT    uMsg,            // Message For This Window
  828.                             WPARAM    wParam,            // Additional Message Information
  829.                             LPARAM    lParam)            // Additional Message Information
  830. {
  831.     switch (uMsg)                                    // Check For Windows Messages
  832.     {
  833.         case WM_ACTIVATE:                            // Watch For Window Activate Message
  834.         {
  835.             if (!HIWORD(wParam))                    // Check Minimization State
  836.             {
  837.                 active=TRUE;                        // Program Is Active
  838.             }
  839.             else
  840.             {
  841.                 active=FALSE;                        // Program Is No Longer Active
  842.             }
  843.  
  844.             return 0;                                // Return To The Message Loop
  845.         }
  846.  
  847.         case WM_SYSCOMMAND:                            // Intercept System Commands
  848.         {
  849.             switch (wParam)                            // Check System Calls
  850.             {
  851.                 case SC_SCREENSAVE:                    // Screensaver Trying To Start?
  852.                 case SC_MONITORPOWER:                // Monitor Trying To Enter Powersave?
  853.                 return 0;                            // Prevent From Happening
  854.             }
  855.             break;                                    // Exit
  856.         }
  857.  
  858.         case WM_CLOSE:                                // Did We Receive A Close Message?
  859.         {
  860.             PostQuitMessage(0);                        // Send A Quit Message
  861.             return 0;                                // Jump Back
  862.         }
  863.  
  864.         case WM_KEYDOWN:                            // Is A Key Being Held Down?
  865.         {
  866.             keys[wParam] = TRUE;                    // If So, Mark It As TRUE
  867.             return 0;                                // Jump Back
  868.         }
  869.  
  870.         case WM_KEYUP:                                // Has A Key Been Released?
  871.         {
  872.             keys[wParam] = FALSE;                    // If So, Mark It As FALSE
  873.             return 0;                                // Jump Back
  874.         }
  875.  
  876.         case WM_SIZE:                                // Resize The OpenGL Window
  877.         {
  878.             ReSizeGLScene(LOWORD(lParam),HIWORD(lParam));  // LoWord=ancho, HiWord=alto
  879.             return 0;                                // Jump Back
  880.         }
  881.         /*case WM_LBUTTONUP:
  882.         {
  883.             botonp=-1;
  884.         }*/
  885.         case WM_LBUTTONDOWN:
  886.             {
  887.                 mouse_x = LOWORD(lParam);          
  888.                 mouse_y = HIWORD(lParam);
  889.                 
  890.                 if(!generando&&!pulsacion&&!fallo&&!triunfo&&!inicio)
  891.                     Pulsa(mouse_x,mouse_y);
  892.                 else if(inicio)
  893.                 {
  894.                     
  895.                     botonp=SelecMenu(mouse_x,mouse_y,0);
  896.                     if(botonp!=-1)
  897.                         PlaySound("data\\boton.WAV",NULL,1);
  898.                     switch(botonp)
  899.                     {
  900.                     case 0:{mnivel=TRUE;
  901.                             inicio=FALSE;
  902.                            }
  903.                         break;
  904.                     case 1:{
  905.                             yo=TRUE;
  906.                             inicio=FALSE;
  907.                            }
  908.  
  909.                         break;
  910.                     case 2:salir=TRUE;
  911.                         break;
  912.                     default:
  913.                         break;
  914.                     }
  915.                 }
  916.                 else if(mnivel)
  917.                 {
  918.                     
  919.                     botonp=SelecMenu(mouse_x,mouse_y,3);
  920.                     if(botonp!=-1)
  921.                     {
  922.                         PlaySound("data\\boton.WAV",NULL,1);
  923.                         nact=botonp;
  924.                         mnivel=FALSE;
  925.                         ReiniciarJuego(nact);
  926.                     }
  927.                 }
  928.                 else if(fallo)
  929.                 {
  930.                     
  931.                     botonp=SelecMenu(mouse_x,mouse_y,0);
  932.                     if(botonp!=-1)
  933.                         PlaySound("data\\boton.WAV",NULL,1);
  934.                     switch(botonp)
  935.                     {
  936.                     case 0:ReiniciarJuego(nact);
  937.                         break;
  938.                     case 1:{inicio=TRUE;
  939.                             fallo=FALSE;
  940.                            }
  941.                         break;
  942.                     case 2:{fallo=FALSE;
  943.                             actual=0;
  944.                             repit=TRUE;
  945.                            }
  946.                         break;
  947.                     default:
  948.                         break;
  949.                     }
  950.                 }
  951.                 else if(yo)
  952.                 {
  953.                     yo=FALSE;
  954.                     inicio=TRUE;
  955.                 }
  956.  
  957.                 if(triunfo)
  958.                 {
  959.                     botonp=SelecMenu(mouse_x,mouse_y,0);
  960.                     if(botonp!=-1)
  961.                         PlaySound("data\\boton.WAV",NULL,1);
  962.                     switch(botonp)
  963.                     {
  964.                     case 0:{
  965.                             nact++;
  966.                             if(nact==6)
  967.                                 salir=TRUE;
  968.                             else
  969.                                 ReiniciarJuego(nact);
  970.                            }
  971.                         break;
  972.                     case 1:{
  973.                         inicio=TRUE;
  974.                         triunfo=FALSE;
  975.                            }
  976.                         break;
  977.                     case 2:salir=TRUE;
  978.                         break;
  979.                     default:
  980.                         break;
  981.                     }
  982.                 }
  983.  
  984.             }
  985.         break;
  986.  
  987.         case WM_MOUSEMOVE:
  988.             {
  989.                 mouse_x = LOWORD(lParam);          
  990.                 mouse_y = HIWORD(lParam);
  991.             }
  992.         break;
  993.     }
  994.  
  995.     // Pass All Unhandled Messages To DefWindowProc
  996.     return DefWindowProc(hWnd,uMsg,wParam,lParam);
  997. }
  998.  
  999. int WINAPI WinMain(    HINSTANCE    hInstance,            // Instance
  1000.                     HINSTANCE    hPrevInstance,        // Previous Instance
  1001.                     LPSTR        lpCmdLine,            // Command Line Parameters
  1002.                     int            nCmdShow)            // Window Show State
  1003. {
  1004.     MSG        msg;                                    // Windows Message Structure
  1005.     BOOL    done=FALSE;                                // Bool Variable To Exit Loop
  1006.     
  1007.  
  1008.     
  1009.     // Ask The User Which Screen Mode They Prefer
  1010.     /*if (MessageBox(NULL,"Would You Like To Run In Fullscreen Mode?", "Start FullScreen?",MB_YESNO|MB_ICONQUESTION)==IDNO)
  1011.     {
  1012.         fullscreen=FALSE;                            // Windowed Mode
  1013.     }*/
  1014.  
  1015.     mireloj=new reloj;
  1016.     //ShowCursor(FALSE);
  1017.     //GLint    viewport[4];
  1018.     //glGetIntegerv(GL_VIEWPORT, viewport);
  1019.     //SetCursorPos(viewport[2]/2,viewport[3]/2);
  1020.     // Create Our OpenGL Window
  1021.     fullscreen=TRUE;
  1022.     if (!CreateGLWindow("Simon",800,600,16,fullscreen))
  1023.     {
  1024.         return 0;                                    // Quit If Window Was Not Created
  1025.     }
  1026.     
  1027.                     
  1028.     while(!done)                                    // Loop That Runs While done=FALSE
  1029.     {
  1030.         if (PeekMessage(&msg,NULL,0,0,PM_REMOVE))    // Is There A Message Waiting?
  1031.         {
  1032.             if (msg.message==WM_QUIT)                // Have We Received A Quit Message?
  1033.             {
  1034.                 done=TRUE;                            // If So done=TRUE
  1035.             }
  1036.             else                                    // If Not, Deal With Window Messages
  1037.             {
  1038.                 TranslateMessage(&msg);                // Translate The Message
  1039.                 DispatchMessage(&msg);                // Dispatch The Message
  1040.             }
  1041.         }
  1042.         else                                        // If There Are No Messages
  1043.         {
  1044.             // Draw The Scene.  Watch For ESC Key And Quit Messages From DrawGLScene()
  1045.             if (active)                                // Program Active?
  1046.             {
  1047.                 if (keys[VK_ESCAPE])                // Was ESC Pressed?
  1048.                 {
  1049.                     done=TRUE;                        // ESC Signalled A Quit
  1050.                 }
  1051.                 else                                // Not Time To Quit, Update Screen
  1052.                 {                
  1053.                     if(salir)
  1054.                         done=TRUE;
  1055.                     DrawGLScene();                    // Draw The Scene
  1056.                     SwapBuffers(hDC);                // Swap Buffers (Double Buffering)
  1057.                 }
  1058.             }                    
  1059.             
  1060.         }
  1061.     }
  1062.  
  1063.     // Shutdown
  1064.     KillGLWindow();                                    // Kill The Window
  1065.     return (msg.wParam);                            // Exit The Program
  1066. }
  1067.  
  1068.  
  1069.  
  1070.